<?php

namespace App\Http\Controllers\Auth;

use App\Exceptions\OperateFailedException;
use App\Helper\SendRequest;
use App\Models\Order;
use App\Models\User;
use GuzzleHttp\Client;
use Illuminate\Http\Request;
use App\Http\Controllers\Controller;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Log;
use mysql_xdevapi\Exception;
use Overtrue\Pinyin\Pinyin;
use Tymon\JWTAuth\Facades\JWTAuth;
use Illuminate\Support\Facades\Cache;

class AuthController extends Controller
{
    use SendRequest;

    public function __construct()
    {
        $this->middleware('auth:api')->except('getCode');
    }

    /* 响应小程序返回session_key
     * 使用微信SDK对session_key进行解密获取用户信息
     *
     * @param code 获取session_key
     * @param iv\encryptedData 解密
     * @param userData 用户信息
     * @return session_key
     */
    public function getCode(Request $request){
        $code = $request->get('code');
        $iv = $request->get('iv');
        $encryptedData = $request->get('encryptedData');
        $appid = env('WX_APPID_3');
        $secret = env('WX_SECRET_3');

        $url = "https://api.weixin.qq.com/sns/jscode2session?appid=".$appid."&secret=".$secret."&js_code=".$code."&grant_type=authorization_code";
        $data = $this->sendRequst('GET', $url);

        $session_key = $data->session_key;
        $openid = $data->openid;

        $userInfo = new \WXBizDataCrypt($appid, $session_key);
        $errCode = $userInfo->decryptData($encryptedData, $iv, $userData);

        if ($errCode == 0) {
            DB::beginTransaction();
            try{
                Log::info($userData);
                $token = $this->insertOrUpdate($userData);
                DB::commit();
            }catch (\Exception $exception){
                DB::rollBack();
                throw new OperateFailedException();
            }
        }else { //未能正常解码获取用户信息
            throw new OperateFailedException('ERROR | user info can not be decoded successfully');
        }



        return $this->responseSuccess($token);
    }

    /* 插入或更新对象 并生成token
     *
     * @param userData
     * @return token
     * @throw OperateFailedException
     */
    private function insertOrUpdate($userData)
    {
        $userInfo = json_decode($userData);

        $openid = $userInfo->openId;
        $name = $userInfo->nickName;
        $sex = $userInfo->gender;
        $avatar = $userInfo->avatarUrl;

        $user = User::where('openID',$openid)->first();

        $data = ['openID'=> $openid, 'name'=>$name, 'sex'=> $sex, 'avatar'=> $avatar];

        if (!$user){
            $user = User::create($data);
            if (!$user){
                throw new OperateFailedException();
            }
        }
        else{
            try{
                $user->update($data);
                $user = User::where('openID',$openid)->first();
            }catch (\Exception $exception){
                throw new OperateFailedException();
            }
        }

        //返回并保存token
        $token = JWTAuth::fromUser($user);
//        \Redis::set($openid, $token);
//        \Redis::expire($openid,2678400);

        $empty = empty($user->phone);
        $response = ['token' => $token, 'openid' => $openid, 'empty' => $empty];
        return $response;
    }

    //检验Token是否可用
    public function checkToken()
    {
        $user = Auth::user();
        $empty = empty($user->phone);
        $res = ['empty' => $empty];
        return $this->responseSuccess($res,'令牌有效');
    }

    /* 退出登入状态,token失效
     *
     * @return \Illuminate\Http\JsonResponse
     * @throw OperateFailedException
     */
    public function logout(){
        if (!JWTAuth::parseToken()->invalidate()){
            throw new OperateFailedException();
        }
        return $this->responseSuccess();
    }

    //测试
    public function phpinfo(){
//         phpinfo();
    }


}
